package cn.qu.phizline.activity;

import android.annotation.TargetApi;
import android.app.Activity;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.os.Build;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.view.Window;
import android.view.WindowManager;
import android.widget.Toast;

import org.webrtc.EglBase;
import org.webrtc.IceCandidate;
import org.webrtc.RendererCommon;
import org.webrtc.SessionDescription;
import org.webrtc.StatsReport;
import org.webrtc.SurfaceViewRenderer;
import org.webrtc.VideoRenderer;

import java.util.ArrayList;
import java.util.List;

import cn.qu.phizline.PhizlineApplication;
import cn.qu.phizline.R;
import cn.qu.phizline.connect.AppRTCClient;
import cn.qu.phizline.connect.peer.PeerConnectionClient;

public class CallActivity extends Activity implements IntentExtraKeys, AppRTCClient.SignalingEvents, PeerConnectionClient.PeerConnectionEvents {

    private static final String TAG = CallActivity.class.getSimpleName();

    //小窗视频
    private SurfaceViewRenderer windowRenderer;

    //全屏视频
    private SurfaceViewRenderer fullscreenRenderer;

    private final ProxyRenderer remoteProxyRenderer = new ProxyRenderer();
    private final ProxyRenderer localProxyRenderer = new ProxyRenderer();

    private final List<VideoRenderer.Callbacks> remoteRenderers = new ArrayList<VideoRenderer.Callbacks>();

    private EglBase rootEglBase;

    // 强制要求开启的应用权限列表
    private static final String[] MANDATORY_PERMISSIONS = {
            "android.permission.MODIFY_AUDIO_SETTINGS",
            "android.permission.RECORD_AUDIO",
            "android.permission.INTERNET"};


    //房间参数
    private AppRTCClient.RoomConnectionParameters roomConnectionParameters;

    private PeerConnectionClient peerConnectionClient;

    private AppRTCClient appRTCClient;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        this.appRTCClient = PhizlineApplication.getClient();

        //设置全屏显示
        requestWindowFeature(Window.FEATURE_NO_TITLE);
        getWindow().addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN | WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON
                | WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD | WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED
                | WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON);
        getWindow().getDecorView().setSystemUiVisibility(getSystemUiVisibility());

        //添加页面显示布局
        setContentView(R.layout.activity_call);

        //视频显示组件
        windowRenderer = (SurfaceViewRenderer) findViewById(R.id.window_video_view);
        fullscreenRenderer = (SurfaceViewRenderer) findViewById(R.id.fullscreen_video_view);

        //添加远程渲染对象
        remoteRenderers.add(remoteProxyRenderer);

        //意图对象
        final Intent intent = getIntent();

        // 创建视频渲染器
        rootEglBase = EglBase.create();
        windowRenderer.init(rootEglBase.getEglBaseContext(), null);
        windowRenderer.setScalingType(RendererCommon.ScalingType.SCALE_ASPECT_FIT);

        fullscreenRenderer.init(rootEglBase.getEglBaseContext(), null);
        fullscreenRenderer.setScalingType(RendererCommon.ScalingType.SCALE_ASPECT_FILL);

        //???
        windowRenderer.setZOrderMediaOverlay(true);
        //???
        windowRenderer.setEnableHardwareScaler(true /* enabled */);
        //???
        fullscreenRenderer.setEnableHardwareScaler(true /* enabled */);


        // 检查必要应用权限
        for (String permission : MANDATORY_PERMISSIONS) {
            if (checkCallingOrSelfPermission(permission) != PackageManager.PERMISSION_GRANTED) {
                logAndToast("无应用权限: " + permission);
                setResult(RESULT_CANCELED);
                finish();
                return;
            }
        }


        // 获取房间服务器URL
        String roomURL = intent.getStringExtra(ROOM_URL);
        Log.d(TAG, "Room URL: " + roomURL);
        if (roomURL == null || roomURL.length() == 0) {
            logAndToast("无法从Intent中找到房间服务器URL");
            setResult(RESULT_CANCELED);
            finish();
            return;
        }
        // 获取房间ID
        String roomId = intent.getStringExtra(ROOM_ID);
        Log.d(TAG, "Room ID: " + roomId);
        if (roomId == null || roomId.length() == 0) {
            logAndToast("无法从Intent中找到房间ID");
            setResult(RESULT_CANCELED);
            finish();
            return;
        }

        //房间参数
        roomConnectionParameters = new AppRTCClient.RoomConnectionParameters(roomURL, roomId);

        PeerConnectionClient.PeerConnectionParameters peerConnectionParameters =
                new PeerConnectionClient.PeerConnectionParameters(
                        true, false, false, 0, 0, 0, 0, "VP8", true, false, 0, "OPUS", false, false, false, false, false, false, false, false
                );

        peerConnectionClient = PeerConnectionClient.getInstance();
        peerConnectionClient.createPeerConnectionFactory(getApplicationContext(), peerConnectionParameters, this);

        startCall();
    }

    private void startCall() {
        if (appRTCClient == null) {
            Log.e(TAG, "AppRTC client is not allocated for a call.");
            return;
        }

        // 开始连接房间服务器
        logAndToast("正在连接: " + roomConnectionParameters.roomUrl);
        appRTCClient.connectToRoom(roomConnectionParameters);
    }

    @TargetApi(19)
    private static int getSystemUiVisibility() {
        int flags = View.SYSTEM_UI_FLAG_HIDE_NAVIGATION | View.SYSTEM_UI_FLAG_FULLSCREEN;
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
            flags |= View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY;
        }
        return flags;
    }

    @Override
    public void onConnectedToRoom(AppRTCClient.SignalingParameters params) {

    }

    @Override
    public void onRemoteDescription(SessionDescription sdp) {

    }

    @Override
    public void onRemoteIceCandidate(IceCandidate candidate) {

    }

    @Override
    public void onRemoteIceCandidatesRemoved(IceCandidate[] candidates) {

    }

    @Override
    public void onChannelClose() {

    }

    @Override
    public void onChannelError(String description) {

    }

    @Override
    public void onLocalDescription(SessionDescription sdp) {

    }

    @Override
    public void onIceCandidate(IceCandidate candidate) {

    }

    @Override
    public void onIceCandidatesRemoved(IceCandidate[] candidates) {

    }

    @Override
    public void onIceConnected() {

    }

    @Override
    public void onIceDisconnected() {

    }

    @Override
    public void onPeerConnectionClosed() {

    }

    @Override
    public void onPeerConnectionStatsReady(StatsReport[] reports) {

    }

    @Override
    public void onPeerConnectionError(String description) {

    }

    private class ProxyRenderer implements VideoRenderer.Callbacks {
        private VideoRenderer.Callbacks target;

        synchronized public void renderFrame(VideoRenderer.I420Frame frame) {
            if (target == null) {
                Log.d(TAG, "Dropping frame in proxy because target is null.");
                VideoRenderer.renderFrameDone(frame);
                return;
            }

            target.renderFrame(frame);
        }

        synchronized public void setTarget(VideoRenderer.Callbacks target) {
            this.target = target;
        }
    }

    private void logAndToast(String message) {
        Log.e(TAG, message);
        Toast.makeText(this, message, Toast.LENGTH_LONG).show();
    }
}
